﻿using Android.Hardware.Display;
using Android.Media.Projection;
using Android.Media;
using Android.Util;
using Android.Graphics;
using Android.OS;
using Android.App;
using Android.Content;
using Android.Views;
using Android.Runtime;
using System.Threading.Tasks;
using System.Text.Json.Nodes;

namespace ScreenShotDemo
{
    /// <summary>
    /// 截图类
    /// </summary>
    public class CaptureScreenHelper
    {
        private const int NotificationId = 1001;
        private MediaProjection? _mediaProjection;
        private VirtualDisplay? _virtualDisplay;
        private ImageReader? _imageReader;
        private DisplayMetrics? _metrics;
        private static CaptureScreenHelper? _instance;
        /// <summary>
        /// 实例化截图类
        /// </summary>
        /// <param name="_service"></param>
        public CaptureScreenHelper(Service _service, int resultCode, Intent data)
        {
            // 初始化
            InitializeCapture(_service, resultCode, data);
        }

        public static CaptureScreenHelper GetCaptureScreenHelper(Service _service, int resultCode, Intent data)
        {
            if (_instance == null) {
                _instance = new CaptureScreenHelper(_service, resultCode, data);
            }
            return _instance;
        }

        /// <summary>
        /// 初始化截图所需相关对象
        /// </summary>
        private void InitializeCapture(Service _service, int resultCode, Intent data)
        {
            CreateNotificationChannel(_service);
            // 前台服务通知
            var notification = new Notification.Builder(_service, "capture_channel")
                .SetContentTitle("截图")
                .SetPriority((int)NotificationPriority.Max)
                .Build();
            _service.StartForeground(NotificationId, notification);
            // 初始化MediaProjection
            DisplayMetrics displayMetrics = getDisplayMetrics(_service);
            // 单缓冲ImageReader（只保留1帧）
            _imageReader = ImageReader.NewInstance(
                displayMetrics.WidthPixels,
                displayMetrics.HeightPixels,
                (ImageFormatType)0x1,//数据流返回得是0X1格式的图片//ImageFormatType.,
                maxImages: 1);//最大图像数1个
            // 注册 ImageReader 回调
            //_imageReader?.SetOnImageAvailableListener(new ImageAvailableListener(), null);
            // 获取MediaProjection实例
            var mgr = _service.GetSystemService(Context.MediaProjectionService) as MediaProjectionManager;
            _mediaProjection = mgr.GetMediaProjection(resultCode, data);
            // 创建VirtualDisplay
            _virtualDisplay = _mediaProjection.CreateVirtualDisplay(
                "ScreenCapture",
                displayMetrics.WidthPixels,
                displayMetrics.HeightPixels,
                (int)_metrics.DensityDpi,
                DisplayFlags.None,
                _imageReader.Surface,
                null,
                null);
        }
        /// <summary>
        /// 创建通知渠道
        /// </summary>
        /// <param name="_service"></param>
        private void CreateNotificationChannel(Service _service)
        {

            if (Build.VERSION.SdkInt < BuildVersionCodes.O) return;
            var channel = new NotificationChannel(
                "capture_channel",
                "Screen Capture",
                NotificationImportance.Low);

            var manager = _service.GetSystemService(Context.NotificationService) as NotificationManager;
            manager?.CreateNotificationChannel(channel);
        }
        /// <summary>
        /// 设置单帧捕获
        /// </summary>
        public Bitmap? setupSingleFrameCapture()
        {
            Image? image = _imageReader?.AcquireLatestImage();
            if (image == null) return null;
            CommUtils.WriteLog($"图像格式{image.Format.ToString()}");
            // 获取图像缓冲区数据
            var planes = image.GetPlanes();
            CommUtils.WriteLog($"图像平面数{planes.Length}");
            if (planes.Length == 0) return null;
            // 获取第一个平面的缓冲区
            var plane = image.GetPlanes()[0];
            var buffer = plane.Buffer;
            int width = image.Width;
            int height = image.Height;
            Bitmap bitmap = Bitmap.CreateBitmap(width, height, Bitmap.Config.Argb8888!);
            buffer.Rewind(); // 重置缓冲区位置
            bitmap.CopyPixelsFromBuffer(buffer);
            //using (var stream = new MemoryStream())
            //
                //bitmap.Compress(Bitmap.CompressFormat.Png, 100, stream);
                //byte[] imageBytess = stream.ToArray();
                //SaveImage(imageBytess);
            //}
            buffer.Dispose();
            // 释放图像资源
            image.Close();//拿到的图片必须关闭，不关闭会内存泄漏，imagerader中的图片不会被释放
            //截图后识别文本
            //裁剪图片
            return bitmap;
        }
        /// <summary>
        /// 保存图片到本地
        /// </summary>
        /// <param name="imageBytes"></param>
        private async void SaveImage(byte[] imageBytes)
        {
            try
            {
                string publicDir = Android.OS.Environment.GetExternalStoragePublicDirectory(
                    Android.OS.Environment.DirectoryPictures).AbsolutePath;
                string filePath = System.IO.Path.Combine(publicDir, "csjt2.jpg");

                // 确保目录存在
                Directory.CreateDirectory(publicDir);

                // 写入文件
                await File.WriteAllBytesAsync(filePath, imageBytes);
            }
            catch (Exception ex)
            {
                Log.Error("ScreenCapture", $"Save failed: {ex.Message}");
            }
        }
        /// <summary>
        /// 获取屏幕分辨率
        /// </summary>
        /// <returns></returns>
        private DisplayMetrics getDisplayMetrics(Service _service)
        {
            if (_metrics != null) return _metrics;
            _metrics = new DisplayMetrics();
            var windowManager = _service.GetSystemService(Context.WindowService)?.JavaCast<IWindowManager>();
            windowManager?.DefaultDisplay?.GetMetrics(_metrics);
            return _metrics;
        }

        internal void Dispose()
        {
            _virtualDisplay?.Release();
            _virtualDisplay?.Dispose();
            _mediaProjection?.Stop();
            _mediaProjection?.Dispose();
            _imageReader?.Dispose();
            _metrics?.Dispose();
        }
    }
}
